#ifndef __GAME_H__
#define __GAME_H__
#define COCOS2D_DEBUG 1

#include "cocos2d.h"
#include "Box2D/Box2D.h"
#include "GeometryUtils.h"
#include "GLES-Render.h"
#include "BodyFactory.h"
#include "Levels/ShapesByLevel.h"
#include "Constants/PhysicsConstants.h"
#include "Model/RaycastHitPoint.h"
#include "Model/Section.h"
#include "Model/BlockShape.h"
#include "SimpleAudioEngine.h"
#include <cmath>

#define DYNAMIC_BODY_FIRST_SHAPE 1
#define DYNAMIC_BODY_SECOND_SHAPE 2


class RayCastCallback : public b2RayCastCallback
{
	public:
		static RayCastCallback* init() {return new RayCastCallback();};
		/*static void delete(RayCastCallback* rayCastCallback) {delete rayCastCallback;
															  rayCastCallback = null;};*/
		virtual float32 ReportFixture (b2Fixture *fixture, const b2Vec2 &point, const b2Vec2 &normal, float32 fraction);
		vector<RaycastHitPoint> getHitPoints(){return hitPoints;};

	private:
		vector<RaycastHitPoint> hitPoints;
};

class Game : public cocos2d::CCLayer
{
public:
	virtual void draw(void);
    // Here's a difference. Method 'init' in cocos2d-x returns bool, instead of returning 'id' in cocos2d-iphone
    virtual bool init();  

    // there's no 'id' in cpp, so we recommand to return the exactly class pointer
    static cocos2d::CCScene* scene();
    
    // a selector callback
    virtual void menuCloseCallback(CCObject* pSender);
	
	

    // implement the "static node()" method manually
    LAYER_CREATE_FUNC(Game);

	// functions
	void drawDebugDraw(bool draw);
	void drawIce();
	void drawFloor();
	void update(float32 dt);
	b2Fixture* queryPoint(b2Vec2& point);
	void runSlicingProcess(cocos2d::CCPoint startPoint, cocos2d::CCPoint endPoint);
	vector<Section> findSections(vector<RaycastHitPoint> firstRayCastHitPoints, vector<RaycastHitPoint> secondRayCastHitPoints);
	void splitHitFixtures(vector<Section>);
	int findPositionInShape(b2Vec2* vertices, int vertexCount, b2Vec2 point);
	int findDynamicBody(b2Vec2 sectionStartPoint, b2Vec2 sectionEndPoint, b2PolygonShape* firstShape);
	void rebuildBlocksFromShapes(vector<BlockShape*> shapes);

	virtual void ccTouchesBegan(cocos2d::CCSet* touches, cocos2d::CCEvent* event);
	virtual void ccTouchesMoved(cocos2d::CCSet* touches, cocos2d::CCEvent* event);
	virtual void ccTouchesEnded(cocos2d::CCSet* touches, cocos2d::CCEvent* event);
	void handleTouchBegan(cocos2d::CCTouch* touch);
	void handleTouchMoved(cocos2d::CCTouch* touch);
	void handleTouchEnded(cocos2d::CCTouch* touch);

	//variables
	/*** GENERIC ***/
	bool mouseDown;
	bool slicing;
	float startX;
	float startY;
	float endX;
	float endY;
	vector<Section> debugSections;

	/*** BOX2D ***/
	GLESDebugDraw* m_b2dDebugDraw;
	b2World* world;
	b2RayCastInput rayCastInput;
	RayCastCallback* firstRayCastCallback;
	RayCastCallback* secondRayCastCallback;

	/*** COCOS2D ***/
	cocos2d::CCPoint lineStartingPoint, lineEndingPoint;
};


#endif  // __GAME_H__
;
